#ifndef DATASTOREIMPL_H_
#define DATASTOREIMPL_H_

#include <map>
#include <string>
#include "datastore.hxx"

class DbEnvImpl;
class DbPartition;
class CompactOption;
class Dbt;
 
//the implementation of DataStore
class DataStoreImpl {

private:
	std::string m_dsname;
	std::string m_dsPath;
	DbEnvImpl* m_env;


    //m_rwlockMap is used for concurrent access to m_partitions map
    pthread_rwlock_t m_rwlockMap;
	std::map<std::string, DbPartition*>* m_partitions;
	uint32_t m_cacheSize;

	uint32_t m_indexArrayCapacity;
	uint32_t m_segmentCapacity;

	//uint32_t m_txnInBuffer;//the number of update not synced yet

    //is the datastore readonly
    bool m_readOnly;
    uint32_t m_flag;
    
	MAPPINGFUNC* m_mapFunc;
	
public:
	DataStoreImpl(DbEnvImpl& env);
    ~DataStoreImpl();

    DbStatus open(const std::string& dsName,
            uint32_t cacheSize,
            uint32_t indexArrayCapacity,
            uint32_t segCapacity,
            MAPPINGFUNC* mapFunc,
            uint32_t flag);

	DbStatus close();

    std::string getDsName(){return m_dsname;}
	std::string getDsPath() {return m_dsPath;}
	uint32_t getIndexArrayCapacity() {return m_indexArrayCapacity; }
	uint32_t getSegCapacity() {return m_segmentCapacity; }
    uint32_t getFlag() {return m_flag;}

    DbStatus addPartition(const std::string& partitionName);
    DbPartition* findPartition(const std::string& partitionName);
    DbStatus removePartition(const std::string& partitionName);

	DbStatus flush();
    DbStatus flushSegments();
    DbStatus flushIndexArray();

	DbStatus get(Dbt& key, Dbt& value);
	DbStatus put(Dbt& key, Dbt& value);
    DbStatus del(Dbt& key);

    DbStatus compact(CompactOption& option);
    void switchEntries();

private:
	//read all of partitions in the datastore directory
	DbStatus init();

};


#endif
